extends Control

signal success_game() #定义信号 开始游戏
signal lose_game() #定义信号 游戏失败

#预加载资源对象---start
const MAHJONG_SCENE = preload("res://GameScenes/MahjongScene/Mahjong.tscn")
#预加载资源对象---end

#实例化class类---start
var scoreMapping = ScoreMapping.new()
#实例化class类---end

#节点加载---start
@onready var hand_container = $HandContainer
@onready var discard_button = $DiscardButton #出牌按钮
@onready var abandon_button = $AbandonButton #弃牌按钮
@onready var hu_button = $HuButton #胡牌按钮
@onready var remainingCardNumber = $RemainingCardNumber #剩余牌数
@onready var scoreLabel = $ScoreBackGround/Score #回合得分
@onready var playing_score_label = $ScoreDetail/ScoreBG/Score_Label #出牌分数
@onready var playing_magnification_label = $ScoreDetail/MagBG/Magnification_Label #出牌倍率
@onready var target_score = $TargetScoreBG/TargetScore #目标分数
@onready var add_score = $AddScore #加分
@onready var add_mag = $AddMag #加倍率
@onready var discard_detail = $DiscardDetail #出牌区域
@onready var func_cards_container = $FuncCardsContainer #功能牌区域
@onready var add_detail = $AddDetail #出牌label详细
@onready var red_fire = $RedFire # 红火
@onready var yellow_fire = $YellowFire # 黄火
@onready var red_fire2 = $RedFire2 # 红火
@onready var yellow_fire2 = $YellowFire2 # 黄火
@onready var timer = $Timer # 计时器 0.5
@onready var timer_1 = $Timer_1s # 计时器 1
@onready var success_or_lose = $SuccessOrLose #你做什么都会成功
@onready var nocp_label = $Numbers/NOCP #出牌次数
@onready var noac_label = $Numbers/NOAC #弃牌次数

@onready var i_have_money = $IHaveMoney #金币结算节点
@onready var c_money = $IHaveMoney/CurrentMoney #当前持有
@onready var i_money = $IHaveMoney/InterestMoney #利息
@onready var w_money = $IHaveMoney/WinMoney #本回合赢得
@onready var e_money = $IHaveMoney/ExtraMoney #额外（功能牌加成）
@onready var f_money = $IHaveMoney/FinalMoney #最终
@onready var next_round = $IHaveMoney/NextRound #下一回合

@onready var round_skill_bg = $RoundSkillBG #庄背景
@onready var round_skill_lable = $RoundSkillBG/RoundSkillLabel #庄技能

@onready var score_mapping_detail = $ScoreMappingDetail #分数对照表

@onready var propsModel = $PropsBG #选择道具区域
@onready var props_container = $PropsBG/PropsContainer
@onready var player_props = $PlayerProps
#节点加载---end

var currentDeck = [] #牌堆
var funcCards = [] #玩家功能牌ID
var funcProps = [] #玩家道具ID
var funcCardsObjArr = [] #玩家功能牌实例
var funcPropsObjArr = [] #玩家道具实例
var selectedMahjongs = [] #存储选择的牌
var handConst = [] #手牌
var currentScoreMapping; #牌型分对照表
var currentMagnification; #牌型倍率对照表
var gameProgress = 1; #1-->整个回合开始， 2-->单次出牌结算时， 3-->单次出牌结算整体结束， 4-->整个回合结束
var beginScore #每次出牌时的初始分（上次出牌结束后的分数）
var finalScore #出牌后最终分
var playingScore = 0 #出牌分数计算
var playingMagnification = 0 #出牌倍率计算
var currentRound #当前回合
var nocp = 5 #Number of card plays（出牌次数）
var noac = 5 #Number of abandoned cards（弃牌次数）
var maxSelected = 6 #最大出牌数量


# 排序顺序：wan, tong, tiao, dong, nan, xi, bei, hongzhong, facai, baiban
var typePriority = {
	"wan": 1,
	"tong": 2,
	"tiao": 3,
	"dong": 4,
	"nan": 5,
	"xi": 6,
	"bei": 7,
	"hongzhong": 8,
	"facai": 9,
	"baiban": 10
}

func _ready():
	currentRound = getRoundById() #获取当前round
	getRoundDetail() #更新渲染回合相关
	updateNocpNoac() #更新出牌/弃牌次数
	finalScore = 0 #初始化玩家分数
	beginScore = finalScore
	currentScoreMapping = scoreMapping.scoreMapping #初始化牌型分
	currentMagnification = scoreMapping.magnificationMapping #初始化牌型倍率
	funcCards = PlayerDetail.currentCarryFunctionCardDeck # 获取持有功能牌
	funcProps = PlayerDetail.currentCarryFunctionProps # 获取持有道具
	funcCardsObjArr = [] # 清空功能牌实例
	funcPropsObjArr= [] # 清空道具实例
	showFuncCards(funcCards) # 渲染功能牌
	showProps(funcProps,player_props) # 渲染道具
	await runFuncCards(funcCardsObjArr,'') # Run功能牌
	await runFuncProps(funcPropsObjArr,'') # Run道具
	currentDeck = PlayerDetail.playerDeck.duplicate()  # 将玩家牌库赋给当前回合(使用深拷贝)
	currentDeck.shuffle() # 打乱牌堆，使得每一次进来的排序都不一样
	handConst = drawMahjongs(14) #初始化手牌
	updateRemainingCardNumber() #更新牌堆数目
	updateScoreLabel() #更新分数
	showHand(handConst) #展示手牌
	showOrhideHuButton()
	gameProgress = 2 #将游戏进程改为等待出牌
	#初始化 按钮绑定事件---start
	discard_button.connect("pressed", Callable(self, "_onDiscardButtonPressed"))
	abandon_button.connect("pressed", Callable(self, "_onAbandonButtonPressed"))
	hu_button.connect("pressed", Callable(self, "_onHuButtonPressed"))
	#初始化 按钮绑定事件---end

	#如果是庄回合，随机调用一个庄的技能
	if RoundDetail.currentSmallRound == 5:
		var randomSkill = getRandomMethod()
		call(randomSkill)
		await get_tree().create_timer(2).timeout  # 等待
		round_skill_bg.visible = false
	

#更新出牌/弃牌次数
func updateNocpNoac():
	nocp_label.text = "出牌" + "\n" + str(nocp)
	noac_label.text = "弃牌" + "\n" + str(noac)

#获取通过id获取当前回合
func getRoundById():
	var roundId = str(RoundDetail.currentBigRound) + "-" + str(RoundDetail.currentSmallRound)
	for item in RoundDetail.rounds:
		if item["roundId"] == roundId:
			return item  # 返回匹配的元素

#获取回合详情
func getRoundDetail():
	target_score.text = "目标分数：" + "\n" + str(currentRound.targetScore)

#显示出牌/弃牌按钮
func showButton():
	discard_button.visible = true
	abandon_button.visible = true
	
#隐藏出牌/弃牌按钮
func hideButton():
	discard_button.visible = false
	abandon_button.visible = false

#抽牌
func drawMahjongs(count: int) -> Array:
	var result = []
	for i in range(count):
		if currentDeck.size() > 0:
			result.append(currentDeck.pop_front())
	return result

#展示手牌
func showHand(mahjongs: Array):
	clear_container(hand_container)
	sortHand(mahjongs) #排序
	for mahjongId in mahjongs:
		var mahjong = MAHJONG_SCENE.instantiate()
		var mahjongType = mahjongId.split("_")[0] + "_" + mahjongId.split("_")[1]  # 获取 ID 的前缀
		mahjong.mahjong_id = mahjongId
		mahjong.mahjong_type = mahjong.typeToChinese[mahjongType]
		#Callable为每张牌添加事件
		mahjong.connect("pressed", Callable(self, "_onMahjongPressed").bind(mahjong))
		hand_container.add_child(mahjong)

# 对手牌进行排序
func sortHand(mahjongs: Array) -> void:
	#使用godot提供的排序方法sort_custom调用自定义compareMahjong方法实现排序具体要求
	mahjongs.sort_custom(Callable(self, "compareMahjong"))

#排序具体规则
func compareMahjong(a: String, b: String) -> int:
	var typeA = a.split("_")[0]  # 获取牌型
	var typeB = b.split("_")[0]
	var numberA = a.split("_")[1]
	var numberB = b.split("_")[1]
	# 按优先级排序
	if typePriority[typeA] < typePriority[typeB]:
		return true  # a 排在 b 前
	elif typePriority[typeA] > typePriority[typeB]:
		return false  # b 排在 a 前
	else:
		if numberA < numberB:
			return true # a 排在 b 前
		elif numberA > numberB:
			return false # b 排在 a 前
		else:
			return false; # 完全相同 不做改变

#补充手牌
func updateHand():
	var handSize = hand_container.get_child_count()
	if handSize < 14:
		var supplementaryHand = drawMahjongs(14 - handSize)
		handConst.append_array(supplementaryHand)
		showHand(handConst)

#更新剩余牌的数目
func updateRemainingCardNumber():
	remainingCardNumber.text = "剩余牌数：" + str(currentDeck.size())

#更新最终回合分数
func updateScoreLabel():
	scoreLabel.text = "回合分数：" + "\n" + str(finalScore)

#更新出牌分数
func updatePlayingScoreLabel():
	timer.start() #启动计时器
	await timer.timeout # 等待
	playing_score_label.text = str(playingScore)
	timer.start() #启动计时器
	await timer.timeout # 等待

#更新出牌倍率
func updatePlayingMagnificationLabel():
	timer.start() #启动计时器
	await timer.timeout # 等待
	playing_magnification_label.text = str(playingMagnification)
	timer.start() #启动计时器
	await timer.timeout # 等待

#结算金币
func changeMoney():
	i_have_money.visible = true
	timer_1.start() #启动计时器
	await timer_1.timeout # 等待
	#展示当前持有money
	c_money.text = "当前:" + str(PlayerDetail.playerMoney)
	timer_1.start() #启动计时器
	await timer_1.timeout # 等待
	# 1.上回合利息，每5金币，得1利息
	var interest = PlayerDetail.playerMoney / 5
	i_money.text = "利息:" + str(interest)
	timer_1.start() #启动计时器
	await timer_1.timeout # 等待
	# 2.
	#2.1剩余出牌次数 = 要加的金币数
	#2.2赢得小回合 +2 赢得庄 +4
	var winMoney = nocp
	if RoundDetail.currentSmallRound != 5:
		winMoney += 2
	else:
		winMoney += 4
	w_money.text = "赢得:" + str(winMoney)
	timer_1.start() #启动计时器
	await timer_1.timeout # 等待
	# 3.看看是否有功能牌额外添加的金币
	var extraMoney = 0
	e_money.text = "额外:" + str(extraMoney)
	timer_1.start() #启动计时器
	await timer_1.timeout # 等待
	# 4.最终金币
	PlayerDetail.playerMoney = PlayerDetail.playerMoney + interest + winMoney + extraMoney
	f_money.text = "最终:" + str(PlayerDetail.playerMoney)
	timer_1.start() #启动计时器
	await timer_1.timeout # 等待
	
	next_round.visible = true
	

#展示出牌
func displayDiscardDetail(selectedMahjongs):
	var mahjongIds = []
	for item in selectedMahjongs:
		var mahjongId = item.mahjong_id
		mahjongIds.append(mahjongId)
	sortHand(mahjongIds) # 对打出的牌排序
	for item in mahjongIds:
		var mahjong = MAHJONG_SCENE.instantiate()
		var mahjongType = item.split("_")[0] + "_" + item.split("_")[1]  # 获取 ID 的前缀
		mahjong.mahjong_id = item
		mahjong.mahjong_type = mahjong.typeToChinese[mahjongType]
		discard_detail.add_child(mahjong)

# 展示功能牌
func showFuncCards(funcCards):
	for item in funcCards:
		# 拼接功能牌场景路径
		var scenePath = "res://GameScenes/FunctionCardScene/" + item + "/" + item + ".tscn"
		# 加载场景并确保返回的是一个 PackedScene
		var funcCardScene = load(scenePath)
		# 检查是否是 PackedScene 类型
		if funcCardScene and funcCardScene is PackedScene:  
			# 实例化场景
			var funcCardInstance = funcCardScene.instantiate()
			if funcCardInstance:
				# 将场景实例添加到当前场景中
				funcCardsObjArr.append(funcCardInstance)
				func_cards_container.add_child(funcCardInstance)
			else:
				print("===未找到该资源===")
		else:
			print("===未找到该资源===")

#功能牌方法整体调用
func runFuncCards(funcCardsObjArr,selectedCardsDetail):
	for item in funcCardsObjArr:
		if gameProgress == item.trigger_timing:
			await item.cardFunction(PlayerDetail.playerDeck,scoreMapping,selectedCardsDetail)

#功能道具方法整体调用
func runFuncProps(funcPropsObjArr,selectedCardsDetail):
	for item in funcPropsObjArr:
		if gameProgress == item.trigger_timing:
			await item.propFunction(PlayerDetail.playerDeck,scoreMapping,selectedCardsDetail)

#play/stop fire
func playFire():
	red_fire.emitting = true;
	yellow_fire.emitting = true;

func playFire2():
	red_fire2.emitting = true;
	yellow_fire2.emitting = true;

func stopFire():
	red_fire.emitting = false;
	yellow_fire.emitting = false;
	red_fire2.emitting = false;
	yellow_fire2.emitting = false;

#清空容器
func clear_container(container: Node):
	for c in container.get_children():
		container.remove_child(c)
		c.queue_free()

#事件一览---start==================
# 点击麻将牌事件
func _onMahjongPressed(mahjong: Button):
	if selectedMahjongs.size() > 0:
		showButton()
	else:
		hideButton()
	# 最大选择限制
	if selectedMahjongs.size() >= maxSelected and not selectedMahjongs.has(mahjong):
		return
	# 处理麻将牌的选中/取消选中
	if selectedMahjongs.has(mahjong):
		selectedMahjongs.erase(mahjong)  # 如果已经选中了，再次点击会取消选择
		mahjong.position.y += 20  # 将牌位置向上移动
	else:
		selectedMahjongs.append(mahjong)  # 添加到选择列表
		mahjong.position.y -= 20  # 将牌位置向下移动（恢复原位）
	if selectedMahjongs.size() > 0:
		showButton()
	else:
		hideButton()
	
# 点击出牌按钮事件
func _onDiscardButtonPressed():
	#出牌结算时，禁止按钮交互
	for button in hand_container.get_children():
		if button is Button:
			button.disabled = true  # 禁用按钮的交互
	nocp -= 1
	updateNocpNoac() #更新出牌/弃牌次数
	hideButton()
	if selectedMahjongs.size() > 0:
		#1.展示打出的牌，并将打出的牌从手牌中移除
		displayDiscardDetail(selectedMahjongs)#展示打出的牌
		for mahjong in selectedMahjongs:
			var mahjongId = mahjong.mahjong_id
			handConst.erase(mahjongId)
			hand_container.remove_child(mahjong)
		
		#2.对打出的牌型进行验证，并在验证过程中调用功能牌方法
		#牌型验证/计算分数---start
		await startCheckSelectedMahjongs(selectedMahjongs)
		#3.在验证结束后，将gameprogress更新为3，同时调用triggertiming为3的功能牌方法
		gameProgress = 3
		if playingScore != 0 || playingMagnification != 0:
			await runFuncCards(funcCardsObjArr,'')#结算类功能牌循环调用
			await runFuncProps(funcPropsObjArr,'')#结算类道具循环调用
		#4.功能牌调用结束后，将gameprogress更新为2
		gameProgress = 2
		#牌型验证/计算分数---end
		
		#5.最终更新分数
		await get_tree().create_timer(1).timeout  # 等待
		if(playingScore != 0 || playingMagnification != 0):
			finalScore += (playingScore * playingMagnification)
			updateScoreLabel()  # 更新分数
		
		#6.一切结束后，清除出牌区域，补全手牌，更新牌堆数目
		# 等待后清除所有显示
		timer.start() #启动计时器
		await timer.timeout # 等待
		playingScore = 0 #更新为0
		updatePlayingScoreLabel()
		playingMagnification = 0 #更新为0
		updatePlayingMagnificationLabel()
		add_detail.text = ""
		stopFire()
		beginScore = finalScore # 更新beginScore
		clear_container(discard_detail) # 清除出牌展示区域
		updateHand()  # 更新手牌
		updateRemainingCardNumber() #更新牌堆数目
	
	#7.最终，将打出的牌销毁，并清空 selectedMahjongs 数组
	if selectedMahjongs.size() > 0:
		for mahjong in selectedMahjongs:
			mahjong.queue_free()  # 销毁牌
		selectedMahjongs.clear()  # 清空已选择的牌
	else:
		print("没有选择牌！")
	
	#8.比较分数，是否通关
	if finalScore >= currentRound.targetScore:
		gameProgress = 4
		#调用 gameprogress=4 的功能牌/道具
		await runFuncCards(funcCardsObjArr,'')#gameprogress=4 功能牌循环调用
		await runFuncProps(funcPropsObjArr,'')#gameprogress=4 道具循环调用
		
		success_or_lose.visible = true
		await get_tree().create_timer(1).timeout  # 等待1秒
		success_or_lose.visible = false
		# 结算金币
		await changeMoney()
		# 如果成功，增加小回合
		RoundDetail.currentSmallRound += 1
		# 如果小回合大于 5，增加大回合并重置小回合
		if RoundDetail.currentSmallRound > 5:
			RoundDetail.currentBigRound += 1
			RoundDetail.currentSmallRound = 1  # 重置小回合为 1
	else:
		if nocp == 0:
			success_or_lose.text = "你失败了～"
			success_or_lose.visible = true
			await get_tree().create_timer(1).timeout  # 等待1秒
			emit_signal("lose_game") # 发送信号 整个游戏失败
		else:
			#出牌后，重新验证手牌是否胡牌
			showOrhideHuButton()
# 点击弃牌按钮事件
func _onAbandonButtonPressed():
	#弃牌瞬间，禁止按钮交互
	for button in hand_container.get_children():
		if button is Button:
			button.disabled = true  # 禁用按钮的交互
	noac -= 1
	if noac == 0:
		abandon_button.disabled = true
	updateNocpNoac() #更新出牌/弃牌次数
	hideButton()
	if selectedMahjongs.size() > 0:
		#1.展示弃掉的牌，并将打出的牌从手牌中移除
		displayDiscardDetail(selectedMahjongs)#展示弃掉的牌
		
		for mahjong in selectedMahjongs:
			var mahjongId = mahjong.mahjong_id
			handConst.erase(mahjongId) # 从手牌数组中移除
			hand_container.remove_child(mahjong) # 画面上移除节点
			currentDeck.append(mahjongId) #将弃掉的麻将重新加入牌堆
		currentDeck.shuffle() #重新洗牌
		#2.特殊功能牌调用
		
		#3.一切结束后，清除出牌区域，补全手牌，更新牌堆数目
		# 等待后清除所有显示
		timer.start() #启动计时器
		await timer.timeout # 等待
		stopFire()
		clear_container(discard_detail) # 清除出牌展示区域
		updateHand()  # 更新手牌
		updateRemainingCardNumber() #更新牌堆数目
		
		#4.弃牌后，验证手牌是否胡牌
		showOrhideHuButton()
	
	#4.最终，清空 selectedMahjongs 数组
	if selectedMahjongs.size() > 0:
		selectedMahjongs.clear()  # 清空已选择的牌
	else:
		print("没有选择牌！")

# 点击下一回合事件
func _on_next_round_pressed() -> void:
	emit_signal("success_game")  # 发送信号 下一回合

#选择道具事件
func _onSelect(propSceneInstance):
	var propId = propSceneInstance.prop_id
	PlayerDetail.currentCarryFunctionProps.append(propId)
	clear_container(player_props) #清空区域后重新渲染
	showProps(PlayerDetail.currentCarryFunctionProps,player_props)
	PropDetail.functionPropDeck.erase(propId)
	clear_container(props_container) #清空区域后重新渲染
	propsModel.visible = false #隐藏选择道具栏
#事件一览---end==================

#牌型验证一览---start==================
#调用出牌的牌形验证
func startCheckSelectedMahjongs(selectedMahjongs):
	var addScore # 定义牌型每次加分
	var addMagnification # 定义牌型倍率
	
	# 调用统计对子、碰、杠的函数
	var ppkObj = countPPK(selectedMahjongs)
	var pairCount = ppkObj["pairCount"]
	var pongCount = ppkObj["pongCount"]
	var kanCount = ppkObj["kanCount"]
	
	# 统计大顺、小顺
	var daShunCount = countDaShun(selectedMahjongs)
	var xiaoshunCount = countXiaoShuns(selectedMahjongs)
	
	# 统计中发白组合（同时包含红中、发财、白板才算一个组合）
	var zfbCount = countZhongFaBai(selectedMahjongs)
	
	# 统计东南西北风组合（同时包含东、南、西、北才算一个组合）
	var fengCount = countFengCombo(selectedMahjongs)

	# 构建一个数组，保存所有需要显示的牌型文字（数量大于0的才显示）
	var label_texts = []
	var scoreMapping = {
		"对子": pairCount,
		"碰子": pongCount,
		"杠子": kanCount,
		"大顺子": daShunCount,
		"小顺子": xiaoshunCount,
		"中发白": zfbCount,
		"东南西北": fengCount
	}
	var scoreKeys = {
		"对子": "pair",
		"碰子": "pong",
		"杠子": "kan",
		"大顺子": "daShun",
		"小顺子": "xiaoshun",
		"中发白": "zhongfabai",
		"东南西北": "feng"
	}

	for key in scoreMapping.keys():
		if scoreMapping[key] > 0:
			label_texts.append(key + " X" + str(scoreMapping[key]))

	# 逐个生成 Label，每生成一个 Label 后等待2秒
	for text in label_texts:
		addScore = 0 # 牌型每次加分清零
		addMagnification = 0 # 牌型倍率每次清零
		var label = Label.new()
		label.text = text
		add_detail.text += text + "\n"
		
		# 根据牌型计算加分
		# 从 text 中提取牌型名称（去掉 " X数量" 部分）
		var baseText = text.split(" ")[0]  # 取 "对子"、"碰子" 等
		addScore = scoreMapping[baseText] * currentScoreMapping[scoreKeys[baseText]]
		addMagnification = scoreMapping[baseText] * currentMagnification[scoreKeys[baseText]]
		var selectedCardsDetail = {
			"detail": baseText,
			"count": scoreMapping[baseText],
			"addScore": addScore,
			"addMagnification": addMagnification
		}
		
		# 调用功能牌处理
		await runFuncCards(funcCardsObjArr, selectedCardsDetail) # Run 功能牌
		addScore = selectedCardsDetail.addScore # 根据功能牌更新分数
		# 更新单次出牌分数
		if addScore != 0:
			playingScore += addScore
			await updatePlayingScoreLabel() # 更新出牌分数
			if playingScore > RoundDetail.scoreFire:
				playFire2()
		#=========================================================================
		await runFuncProps(funcPropsObjArr, selectedCardsDetail)# Run 道具
		addMagnification = selectedCardsDetail.addMagnification # 根据功能牌更新倍率
		# 更新单次出牌倍率
		if addMagnification != 0:
			playingMagnification += addMagnification
			await updatePlayingMagnificationLabel() # 更新出牌倍率
			if playingMagnification > RoundDetail.magFire:
				playFire()	

# 统计此次出牌堆中有多少个对子,碰，杠 (只！用于出牌验证)
func countPPK(selectedMahjongs):
	var counts = {}  # 用于存储每种牌的出现次数
	for mahjong in selectedMahjongs:
		var mahjongType = mahjong.mahjong_id.split("_")[0] + "_" + mahjong.mahjong_id.split("_")[1]
		if counts.has(mahjongType):
			counts[mahjongType] += 1
		else:
			counts[mahjongType] = 1
	var pairCount = 0
	var pongCount = 0
	var kanCount = 0
	var usedPairs = {}  # 用于记录已经计算过的对子，避免重复
	# 遍历所有牌类型
	for card_type in counts.keys():
		# 计算对子、碰和杠
		if counts[card_type] >= 2 and not usedPairs.has(card_type):  # 如果是对子且没被计算过
			pairCount += 1
			usedPairs[card_type] = true  # 标记已计算该对子
		if counts[card_type] >= 3:
			pongCount += 1
		if counts[card_type] >= 4:
			kanCount += 1
	var ppkObj = {
		"pairCount": pairCount,
		"pongCount": pongCount,
		"kanCount": kanCount
	}
	return ppkObj
	
# 统计每种牌型的数量
func countMahjongTypes(selectedMahjongs):
	var counts = {}
	for mahjong in selectedMahjongs:
		var mahjongType = mahjong.mahjong_id.split("_")[0] + "_" + mahjong.mahjong_id.split("_")[1]
		counts[mahjongType] = counts.get(mahjongType, 0) + 1
	return counts

# 检查大顺规则
func countDaShun(selectedMahjongs):
	var suitNumbers = {}  # 用于按花色存储数字，键为花色（例如 "tiao"），值为该花色中出现的牌号数组
	# 遍历所有选中的牌，分解牌的ID，并存入对应花色的数组（避免重复）
	for mahjong in selectedMahjongs:
		var parts = mahjong.mahjong_id.split("_")
		var suit = parts[0]         # 花色，如 "tiao"
		var number = int(parts[1])  # 牌号，如 4
		if suitNumbers.has(suit):
			if not suitNumbers[suit].has(number):
				suitNumbers[suit].append(number)
		else:
			suitNumbers[suit] = [number]
	
	# 对每个花色的牌号进行排序，便于查找连续数字
	for suit in suitNumbers.keys():
		suitNumbers[suit].sort()
	
	var daShunCount = 0  # 用于记录大顺的数量
	
	# 遍历每个花色，查找是否存在连续的6张牌
	for suit in suitNumbers.keys():
		var numbers = suitNumbers[suit]
		# 遍历每个花色的牌号，查找是否有 1, 2, 3, 4, 5, 6 连续的牌
		for i in range(0, numbers.size() - 5):  # -5 确保能够有 6 张牌
			if numbers[i+1] == numbers[i] + 1 and numbers[i+2] == numbers[i] + 2 and numbers[i+3] == numbers[i] + 3 and numbers[i+4] == numbers[i] + 4 and numbers[i+5] == numbers[i] + 5:
				daShunCount += 1
	
	return daShunCount

# 检查小顺规则
func countXiaoShuns(selectedMahjongs):
	var suitNumbers = {}  # 用于按花色存储数字，键为花色（例如 "tiao"），值为该花色中出现的牌号数组
	# 遍历所有选中的牌，分解牌的ID，并存入对应花色的数组（避免重复）
	for mahjong in selectedMahjongs:
		var parts = mahjong.mahjong_id.split("_")
		var suit = parts[0]         # 花色，如 "tiao"
		var number = int(parts[1])  # 牌号，如 4
		if suitNumbers.has(suit):
			if not suitNumbers[suit].has(number):
				suitNumbers[suit].append(number)
		else:
			suitNumbers[suit] = [number]
	
	# 对每个花色的牌号进行排序，便于查找连续数字
	for suit in suitNumbers.keys():
		suitNumbers[suit].sort()
	
	var smallShunCount = 0  # 用于记录小顺的数量
	
	# 遍历每个花色，查找是否存在连续的3张牌（小顺）
	for suit in suitNumbers.keys():
		var numbers = suitNumbers[suit]
		# 依次遍历排序后的牌号，检查是否有 num, num+1, num+2 连续的牌
		for i in range(0, numbers.size() - 2):  # -2 确保能够有 3 张牌
			if numbers[i+1] == numbers[i] + 1 and numbers[i+2] == numbers[i] + 2:
				smallShunCount += 1
	
	return smallShunCount

# 检查中发白规则
func countZhongFaBai(selectedMahjongs):
	var normalizedSet = {}
	# 遍历所有选中的牌，标准化并存入字典
	for mahjong in selectedMahjongs:
		var parts = mahjong.mahjong_id.split("_")
		var cardType = parts[0] + "_" + parts[1]  # 如 "hongzhong_1"
		normalizedSet[cardType] = true
	
	# 检查是否有中发白组合
	if normalizedSet.has("hongzhong_1") and normalizedSet.has("facai_1") and normalizedSet.has("baiban_1"):
		return 1  # 如果有中发白的三张组合，返回1
	return 0  # 否则返回0

# 检查东南西北规则
func countFengCombo(selectedMahjongs):
	var normalizedSet = {}
	# 遍历所有选中的牌，标准化并存入字典
	for mahjong in selectedMahjongs:
		var parts = mahjong.mahjong_id.split("_")
		var cardType = parts[0] + "_" + parts[1]  # 如 "dong_1"
		normalizedSet[cardType] = true
	
	# 检查是否有东南西北风组合
	if normalizedSet.has("dong_1") and normalizedSet.has("nan_1") and normalizedSet.has("xi_1") and normalizedSet.has("bei_1"):
		return 1  # 如果有东南西北风的四张组合，返回1
	return 0  # 否则返回0

#牌型验证一览---end==================

# 胡牌相关逻辑-------------------------------------------------------------
# 显示胡牌按钮
func showOrhideHuButton():
	var handConstId = []
	for item in handConst:
		var id = item.split("_")[0] + "_" + item.split("_")[1]
		handConstId.append(id)
	var convertCardId = convert_card_id(handConstId)
	if can_hu(convertCardId,0):
		hu_button.visible = true
	else:
		hu_button.visible = false

#牌id转换
func convert_card_id(cards: Array) -> Array:
	var card_map = {
	"wan_1": 01, "wan_2": 02, "wan_3": 03, "wan_4": 04, "wan_5": 05, "wan_6": 06, "wan_7": 07, "wan_8": 08, "wan_9": 09,
	"tong_1": 11, "tong_2": 12, "tong_3": 13, "tong_4": 14, "tong_5": 15, "tong_6": 16, "tong_7": 17, "tong_8": 18, "tong_9": 19,
	"tiao_1": 21, "tiao_2": 22, "tiao_3": 23, "tiao_4": 24, "tiao_5": 25, "tiao_6": 26, "tiao_7": 27, "tiao_8": 28, "tiao_9": 29,
	"dong_1": 31, "nan_1": 33, "xi_1": 35, "bei_1": 37,
	"hongzhong_1": 41, "facai_1": 43, "baiban_1": 45
	}
	var converted_cards = []
	# 遍历每张牌，将牌转换为对应的数字
	for card in cards:
		if card_map.has(card):  # 如果该牌存在于映射中
			converted_cards.append(card_map[card])
	return converted_cards

#验证胡牌主逻辑----start
func can_hu(cards: Array, laizi_count: int):
	# 如果牌张数不是2、5、8、11、14，则不能胡
	if (cards.size() + laizi_count + 1) % 3 != 0:
		return false
	
	# 排序方便胡牌判断
	cards.sort()

	# 依次删除一对牌做将，其余牌全部成扑则可胡
	for i in range(cards.size()):
		if i > 0 and cards[i] == cards[i - 1]:
			# 和上一次是同样的牌，避免重复计算
			continue
		if i + 1 < cards.size() and cards[i] == cards[i + 1] or laizi_count > 0:
			# 找到对子，或是用一张癞子拼出的对子
			var pu_cards = cards.duplicate()  # 复制牌堆
			var pu_laizi = laizi_count
			pu_cards.remove_at(i)
			
			if pu_cards[i] == cards[i]:
				pu_cards.remove_at(i)
			else:
				pu_laizi -= 1
			
			# 删除对子后，检查剩下的牌是否成扑
			if is_shun_ke(pu_cards, pu_laizi):
				return true
	
	if laizi_count >= 2 and is_shun_ke(cards, laizi_count - 2):
		# 两个癞子做将牌特殊判定处理
		return true
	
	return false

func is_shun_ke(cards: Array, laizi_count: int) -> bool:
	if cards.size() == 0:
		return true
	# 若第一张是顺子中的一张
	for first in range(cards[0] - 2, cards[0] + 1):
		if first % 10 > 7 or (laizi_count == 0 and first < cards[0]):
			continue

		var shun_count = 0
		for i in range(3):
			if cards.find(first + i) >= 0:
				shun_count += 1

		if shun_count == 3 or shun_count + laizi_count >= 3:
			var pu_cards = cards.duplicate()
			var pu_laizi = laizi_count
			for i in range(3):
				var delete_pos = pu_cards.find(first + i)
				if delete_pos >= 0:
					pu_cards.remove_at(delete_pos)
				else:
					pu_laizi -= 1

			if is_shun_ke(pu_cards, pu_laizi):
				return true

	# 若第一张是刻子中的一张
	var kezi_count = 1
	var kezi_card = cards[0]

	if cards[1] == kezi_card:
		kezi_count += 1
	if cards[2] == kezi_card:
		kezi_count += 1

	if kezi_count == 3 or kezi_count + laizi_count >= 3:
		var pu_cards = cards.duplicate()
		var pu_laizi = laizi_count
		for i in range(3):
			var delete_pos = pu_cards.find(kezi_card)
			if delete_pos >= 0:
				pu_cards.remove_at(delete_pos)
			else:
				pu_laizi -= 1

		if is_shun_ke(pu_cards, pu_laizi):
			return true

	return false
#验证胡牌主逻辑----end

# 胡牌按钮事件
func _onHuButtonPressed():
		chooseProp() #选择道具
		handConst.clear()  # 清空手牌
		clear_container(hand_container) # 清除手牌展示区域
		updateHand()  # 更新手牌
		showOrhideHuButton()
		updateRemainingCardNumber() #更新牌堆数目
# 胡牌相关逻辑end-------------------------------------------------------------

# 胡牌后,选择道具
func chooseProp():
	var props = PropDetail.functionPropDeck
	if props.size() > 0:
		var randomPropArr = []
		if props.size() > 3:
			var index1 = randi() % props.size()
			var index2 = randi() % props.size()
			while index1 == index2:
				index2 = randi() % props.size()
			var index3 = randi() % props.size()
			while index2 == index3 || index1 == index3:
				index3 = randi() % props.size()
			randomPropArr = [props[index1], props[index2],props[index3]]
		else:
			if props.size() == 3:
				randomPropArr = [props[0], props[1], props[2]]
			elif props.size() == 2:
				randomPropArr = [props[0], props[1]]
			else:
				randomPropArr = [props[0]]
		showProps(randomPropArr,props_container)
		propsModel.visible = true
	else:
		print("没有道具了")

#展示道具
func showProps(propArr,container):
	funcPropsObjArr = []
	for item in propArr:
		# 拼接道具场景路径
		var scenePath = "res://GameScenes/FunctionPropScene/" + item + "/" + item + ".tscn"
		# 加载场景并确保返回的是一个 PackedScene
		var propScene = load(scenePath)
		# 检查是否是 PackedScene 类型
		if propScene and propScene is PackedScene:  
			# 实例化场景
			var propSceneInstance = propScene.instantiate()
			if propSceneInstance:
				if container == props_container:
					# 创建一个 Container 节点作为容器
					var propContainer = VBoxContainer.new()
					propContainer.custom_minimum_size = Vector2(200,100)
					# 将道具添加到 Control 容器中
					propContainer.add_child(propSceneInstance)
					# 创建选择按钮
					var button = Button.new()
					button.custom_minimum_size = Vector2(0,0)
					button.text = "选择"
					button.connect("pressed", Callable(self, "_onSelect").bind(propSceneInstance))
					propContainer.add_child(button)
					container.add_child(propContainer)
				elif container == player_props:
					container.add_child(propSceneInstance)
					funcPropsObjArr.append(propSceneInstance)
			else:
				print("===未找到该资源===")
		else:
			print("===未找到该资源===")

#定义庄 随机技能--start
func getRandomMethod() -> String:
	round_skill_bg.visible = true
	var methods = ["feature_one", "feature_two", "feature_three"]
	return methods[randi() % methods.size()]  # 随机返回一个方法名称

func feature_one():
	round_skill_lable.text = "庄技能：您的小顺子基础分变为0分" 
	currentScoreMapping.xiaoshun = 0

func feature_two():
	round_skill_lable.text = "庄技能：您的对子基础分变为0分"
	currentScoreMapping.pair = 0
	

func feature_three():
	round_skill_lable.text = "庄技能：您的大顺子基础分变为0分"
	currentScoreMapping.daShun = 0
#定义庄 随机技能--end

func showScoreMappingDetail():
	var scoreMap = scoreMapping.scoreMapping
	var magnificationMap = scoreMapping.magnificationMapping
	var labelStr = ""
	#"pair"
	labelStr = "对子：" + str(scoreMap.pair) + " X " + str(magnificationMap.pair) + "\n"
	#"pong"
	labelStr += "碰子：" + str(scoreMap.pong) + " X " + str(magnificationMap.pong) + "\n"
	#"kan"
	labelStr += "杠子：" + str(scoreMap.kan) + " X " + str(magnificationMap.kan) + "\n"
	#"daShun"
	labelStr += "大顺子：" + str(scoreMap.daShun) + " X " + str(magnificationMap.daShun) + "\n"
	#"xiaoshun"
	labelStr += "小顺子：" + str(scoreMap.xiaoshun) + " X " + str(magnificationMap.xiaoshun) + "\n"
	#"zhongfabai"
	labelStr += "中发白：" + str(scoreMap.zhongfabai) + " X " + str(magnificationMap.zhongfabai) + "\n"
	#"feng"
	labelStr += "东南西北：" + str(scoreMap.feng) + " X " + str(magnificationMap.feng) + "\n"
	score_mapping_detail.text = labelStr

func _on_score_mapping_btn_mouse_entered() -> void:
	showScoreMappingDetail()
	score_mapping_detail.visible = true
	
func _on_score_mapping_btn_mouse_exited() -> void:
	score_mapping_detail.visible = false
